#!/bin/bash

set -e

PERCENTAGES=($(seq 5 5 95))   # You can change this
TIMEOUT_EACH_TEST_CASE_S="60" # You can change this

NUM_PERCENTAGES=${#PERCENTAGES[@]}
MAX_MQ_NUM=$(cat /proc/sys/fs/mqueue/queues_max)
declare -a MQ_PERCENT
for ((i = 0; i < NUM_PERCENTAGES; i++)); do
    MQ_PERCENT[$i]=$((MAX_MQ_NUM * ${PERCENTAGES[i]} / 100))
done
TIMEOUT=680s # based on the measurement time of e2e tests

# Workaround for launch_testing timeout configuration
# This is because it is hard coded in https://github.com/ros2/launch/blob/f31c1ff13fcbed3653d1a0e26438cb739e96d751/launch_testing/launch_testing/test_runner.py#L184.
SED_TARGET_FILE=$(dirname "$(python3 -c 'import launch_testing; print(launch_testing.__file__)')")/test_runner.py
sudo cp $SED_TARGET_FILE $SED_TARGET_FILE.bak
TIMEOUT_WITH_BUFFER=$((TIMEOUT_EACH_TEST_CASE_S + 10))
sudo sed -i '/if not self._processes_launched.wait/s/\(timeout=\)[0-9]\+/\1'"$TIMEOUT_WITH_BUFFER"'/' "$SED_TARGET_FILE"

cleanup() {
    sudo cp $SED_TARGET_FILE.bak $SED_TARGET_FILE
    echo "Stopping stress-ng..."
    pkill -P $$ # Kill all child processes
    exit 1
}

trap cleanup SIGINT

run-stress-ng() {
    if [ $1 -lt $NUM_PERCENTAGES ]; then
        echo "Run stress-ng with CPU load ${PERCENTAGES[$1]}%" | sudo tee /dev/kmsg
        stress-ng --cpu $(nproc) --cpu-load ${PERCENTAGES[$1]} --timeout $TIMEOUT &

    elif [ "$1" -lt "$((NUM_PERCENTAGES * 2))" ]; then
        index=$(($1 - NUM_PERCENTAGES))
        echo "Run stress-ng with VM ${PERCENTAGES[$index]}%" | sudo tee /dev/kmsg
        stress-ng --vm 1 --vm-bytes ${PERCENTAGES[$index]}% --timeout $TIMEOUT &

    else
        index=$(($1 - NUM_PERCENTAGES * 2))
        echo "Run stress-ng with MQ ${MQ_PERCENT[$index]}" | sudo tee /dev/kmsg
        stress-ng --mq ${MQ_PERCENT[$index]} --timeout $TIMEOUT &
    fi
}

NUM_LOOP=$((NUM_PERCENTAGES * 3)) # cpu_load, vm, mq
for i in $(seq 1 $NUM_LOOP); do
    echo "============================================================================" | sudo tee /dev/kmsg
    echo "============================ Outer Loop $i / $NUM_LOOP ============================" | sudo tee /dev/kmsg
    echo "============================================================================" | sudo tee /dev/kmsg

    run-stress-ng $(($i - 1))
    STRESS_TEST_TIMEOUT=$TIMEOUT_EACH_TEST_CASE_S ./scripts/e2e_test_1to1_with_ros2sub
    STRESS_TEST_TIMEOUT=$TIMEOUT_EACH_TEST_CASE_S ./scripts/e2e_test_2to2

    wait
done
